home *** CD-ROM | disk | FTP | other *** search
/ Otherware / Otherware_1_SB_Development.iso / mac / developm / source / divaplug.cpt / VideoShop Plug-In Kit 1.0 / SampleXsn.p < prev   
Encoding:
Text File  |  1992-05-06  |  10.8 KB  |  454 lines

  1. {
  2.  
  3.     SampleXsn.c
  4.     
  5.     Sample transition effect for VideoShop
  6.     
  7.     04/28/92    Ivçn Cavero Bela£nde
  8.     
  9. }
  10.  
  11. UNIT    SampleTransition;
  12.  
  13. INTERFACE
  14.  
  15. USES
  16.     Types,Memory,Resources,QuickDraw,QDOffscreen,Dialogs,OSUtils,Packages,Errors,
  17.     ToolUtils,SysEqu,GestaltEqu,DiVATransition;
  18.  
  19. FUNCTION XsnEntryPoint(selector: INTEGER; params: XsitionParamPtr; VAR data: LONGINT;
  20.     transitionIntensity, maxTransitionIntensity: INTEGER): XsnErr;
  21.  
  22. FUNCTION DoParameters(params: XsitionParamPtr): XsnErr;
  23.  
  24. FUNCTION DoProcessFrame(params: XsitionParamPtr; transitionIntensity,
  25.     maxTransitionIntensity: INTEGER): XsnErr;
  26.  
  27. IMPLEMENTATION
  28.  
  29. CONST
  30.  
  31. {    Dialog item constants    }
  32.  
  33.     dialogID            =    16001;
  34.     defaultItem            =    3;
  35.     leftToRightItem        =    5;
  36.     topToBottomItem        =    6;
  37.     rightToLeftItem        =    7;
  38.     bottomToTopItem        =    8;
  39.     dividerItem            =    10;
  40.  
  41. TYPE
  42.     
  43.     WipeParams = RECORD
  44.         angle:    INTEGER;
  45.     END;
  46.     
  47.     WipeParamPtr = ^WipeParams;
  48.     WipeParamHandle = ^WipeParamPtr;
  49.  
  50.     RGBColorPtr    =    ^RGBColor;
  51.  
  52. FUNCTION XsnEntryPoint(selector: INTEGER; params: XsitionParamPtr; VAR data: LONGINT;
  53.     transitionIntensity, maxTransitionIntensity: INTEGER): XsnErr;
  54. {
  55.     The transition entry point and dispatcher routine. Calls the appropriate
  56.     subroutine based on the selector passed.
  57. }
  58. BEGIN
  59.     CASE selector OF
  60.         XSParameters:
  61.             XsnEntryPoint := DoParameters (params);
  62.         XSPrepare:
  63.             XsnEntryPoint := noErr;
  64.         XSStart:
  65.             XsnEntryPoint := noErr;
  66.         XSProcessFrame:
  67.             XsnEntryPoint := DoProcessFrame(params,transitionIntensity,maxTransitionIntensity);
  68.         XSFinish:
  69.             XsnEntryPoint := noErr;
  70.         OTHERWISE
  71.             XsnEntryPoint := -1;
  72.     END;
  73. END;
  74.  
  75.  
  76. FUNCTION DoTestAbort(codeAddress: ProcPtr): BOOLEAN;
  77. {    Inline code to call the TestAbort function    }
  78.     INLINE    $205F,        {    move.l    (a7)+,a0    pop procPtr from stack    }
  79.             $4E90;        {    jsr        (a0)        and call it                }
  80.  
  81. FUNCTION TestAbort (params: XsitionParamPtr): BOOLEAN;
  82. BEGIN
  83.     TestAbort := DoTestAbort(params^.abortProc);
  84. END;
  85.  
  86. PROCEDURE DoUpdateProgress(done, total: LONGINT; codeAddress: ProcPtr);
  87. {    Inline code to call the UpdateProgress function    }
  88.     INLINE    $205F,        {    move.l    (a7)+,a0    pop procPtr from stack    }
  89.             $4E90;        {    jsr        (a0)        and call it                }
  90.  
  91. PROCEDURE UpdateProgress(params: XsitionParamPtr; done, total: LONGINT);
  92. BEGIN
  93.     DoUpdateProgress(done,total,params^.progressProc);
  94. END;
  95.  
  96. PROCEDURE CenterDialog(dt: DialogTHndl);
  97. {
  98.     Given a dialog template in dt, modify it so as to center the dialog on the
  99.     main device.
  100. }
  101. VAR
  102.     width, height:    INTEGER;
  103.     mainDevice:        GDHandle;
  104.     r,dr:            Rect;
  105. BEGIN
  106.     mainDevice := GetMainDevice;
  107.     r := mainDevice^^.gdRect;
  108.     width := r.right - r.left;
  109.     height := r.bottom - r.top;
  110.     
  111.     dr := dt^^.boundsRect;
  112.     OffsetRect (dr, r.left-dr.left, r.top-dr.top);
  113.     OffsetRect (dr, (width - (dr.right-dr.left)) DIV 2,
  114.                     (height - (dr.bottom-dr.top) - GetMBarHeight) DIV 3 + GetMBarHeight);
  115.     dt^^.boundsRect := dr;
  116. END;
  117.  
  118. PROCEDURE OutlineOK(dp: DialogPtr; item: INTEGER);
  119. {
  120.     userItem drawing routine for outlining the default button in the dialog box
  121. }
  122. VAR
  123.     r:    Rect;
  124.     h:    Handle;
  125.     itemType:    INTEGER;
  126. BEGIN
  127.     item := ok;
  128.     GetDItem (dp, item, itemType, h, r);
  129.     PenNormal;
  130.     PenSize (3, 3);
  131.     InsetRect (r, -4, -4);
  132.     FrameRoundRect (r, 16, 16);
  133.     PenNormal;
  134. END;
  135.  
  136. FUNCTION GetWindowGDevice(w: WindowPtr): GDHandle;
  137. {
  138.     Find the deepest gdevice the window intersects. Used for determining the depth
  139.     of the screen we're drawing on (to look good on B/W displays).
  140. }
  141. VAR
  142.     r:            Rect;
  143.     oldPort:    GrafPtr;
  144. BEGIN
  145.     GetPort(oldPort);
  146.     SetPort(w);
  147.     r := w^.portRect;
  148.     LocalToGlobal(r.topLeft);
  149.     LocalToGlobal(r.botRight);
  150.     GetWindowGDevice := GetMaxDevice(r);
  151.     SetPort (oldPort);
  152. END;
  153.  
  154. PROCEDURE DrawLines(theDialog: DialogPtr; itemNo: INTEGER);
  155. {
  156.     userItem drawing routine for dividing lines (with shadow)
  157. }
  158. VAR
  159.     oldColor, greyColor:    RGBColor;
  160.     itemType:    INTEGER;
  161.     me:            Handle;
  162.     box:        Rect;
  163. BEGIN
  164.     GetDItem(theDialog,itemNo,itemType,me,box);
  165.     GetForeColor(oldColor);
  166.     RGBForeColor(RGBColorPtr(RGBBlack)^);
  167.     MoveTo(box.left,box.top);
  168.     LineTo(box.right-2,box.top);
  169.     MoveTo(box.left,box.top+3);
  170.     LineTo(box.right-2,box.top+3);
  171.     IF (GetWindowGDevice(theDialog)^^.gdPMap^^.pixelSize >= 8) THEN
  172.         BEGIN
  173.             greyColor.red := $7777;
  174.             greyColor.green := $7777;
  175.             greyColor.blue := $7777;
  176.             RGBForeColor (greyColor);
  177.             MoveTo(box.left+1,    box.top+1);
  178.             LineTo(box.right-1,    box.top+1);
  179.             MoveTo(box.left+1,    box.top+4);
  180.             LineTo(box.right-1,    box.top+4);
  181.         END;
  182.     RGBForeColor(oldColor);
  183. END;
  184.  
  185. PROCEDURE SetupDItems (dp: DialogPtr);
  186. VAR
  187.     itemType:    INTEGER;
  188.     h:            Handle;
  189.     r:            Rect;
  190. BEGIN
  191.     {    Point default useritem to default button outline routine    }
  192.     GetDItem (dp, defaultItem, itemType, h                  , r);
  193.     SetDItem (dp, defaultItem, itemType, Handle(@OutlineOK), r);
  194.     
  195.     {    Point divider lines useritem to dividing lines drawing routine    }
  196.     GetDItem (dp, dividerItem, itemType, h                  , r);
  197.     SetDItem (dp, dividerItem,  itemType, Handle(@DrawLines), r);    
  198. END;
  199.  
  200. PROCEDURE TurnAllOffButMe(dp: DialogPtr; itemNo: INTEGER);
  201. {
  202.     Turn off all but one control dialog items in a given range. Used for managing
  203.     sets of radio buttons.
  204. }
  205. VAR
  206.     j,itemType    : INTEGER;
  207.     h:    Handle;
  208.     r:    Rect;
  209. BEGIN
  210.     FOR j:=leftToRightItem TO bottomToTopItem DO
  211.         IF (j <> itemNo) THEN BEGIN
  212.             GetDItem (dp,j,itemType,h,r);
  213.             SetCtlValue(ControlHandle(h),0);
  214.         END;
  215.     GetDItem (dp,itemNo,itemType,h,r);
  216.     SetCtlValue(ControlHandle(h),1);
  217. END;
  218.  
  219. PROCEDURE RecalcDItems (p: WipeParamHandle; dp: DialogPtr);
  220. BEGIN
  221.     CASE p^^.angle OF
  222.         0:
  223.             TurnAllOffButMe(dp,bottomToTopItem);
  224.         90:
  225.             TurnAllOffButMe(dp,leftToRightItem);
  226.         180:
  227.             TurnAllOffButMe(dp,topToBottomItem);
  228.         270:
  229.             TurnAllOffButMe(dp,rightToLeftItem);
  230.         OTHERWISE
  231.             BEGIN
  232.                 TurnAllOffButMe(dp,leftToRightItem);
  233.                 p^^.angle := 90;
  234.             END;
  235.     END;
  236. END;
  237.  
  238. FUNCTION DoParameters (params: XsitionParamPtr): XsnErr;
  239. {
  240.     Prompt the user for parameters if necessary.
  241. }
  242. VAR
  243.     item:    INTEGER;
  244.     dp:        DialogPtr;
  245.     dt:        DialogTHndl;
  246.     theParams:    WipeParamHandle;
  247.  
  248. BEGIN    
  249.     {    If we didn't get passed a params handle, allocate and initialize it    }
  250.     IF (params^.parameters = NIL) THEN BEGIN
  251.         theParams := WipeParamHandle(NewHandleClear(sizeof(WipeParams)));
  252.         IF (theParams = NIL) THEN BEGIN
  253.             DoParameters := XSErrOutOfMemory + MemError;
  254.             Exit(DoParameters);
  255.         END;
  256.         theParams^^.angle := 90;
  257.     END
  258.     ELSE BEGIN
  259.     {
  260.         Otherwise, we just return. If we required specific hardware or mounds of
  261.         memory we would check here.
  262.     }
  263.         DoParameters := noErr;
  264.         Exit(DoParameters);
  265.     END;
  266.     
  267.     {    Load in the dialog and reposition it in the best device    }
  268.     dt := DialogTHndl(GetResource ('DLOG', dialogID));
  269.     HNoPurge (Handle(dt));
  270.     CenterDialog (dt);
  271.     
  272.     {    Show it    }
  273.     dp := GetNewDialog (dialogID, nil, WindowPtr(-1));
  274.     
  275.     {    Setup the user items and initialize all controls to initial state    }
  276.     SetupDItems(dp);
  277.     RecalcDItems(theParams,dp);
  278.     
  279.     REPEAT
  280.         ModalDialog (nil, item);
  281.         CASE item OF
  282.             topToBottomItem:
  283.                 BEGIN
  284.                     theParams^^.angle := 180;
  285.                     RecalcDItems (theParams, dp);
  286.                 END;
  287.             leftToRightItem:
  288.                 BEGIN
  289.                     theParams^^.angle := 90;
  290.                     RecalcDItems (theParams, dp);
  291.                 END;
  292.             bottomToTopItem:
  293.                 BEGIN
  294.                     theParams^^.angle := 0;
  295.                     RecalcDItems (theParams, dp);
  296.                 END;
  297.             rightToLeftItem:
  298.                 BEGIN
  299.                     theParams^^.angle := 270;
  300.                     RecalcDItems (theParams, dp);
  301.                 END;
  302.         END;
  303.     UNTIL ((item = ok) OR (item = cancel));
  304.     
  305.     DisposDialog (dp);
  306.     HPurge (Handle(dt));
  307.     
  308.     IF (item = cancel) THEN BEGIN
  309.         DisposHandle(Handle(theParams));
  310.         params^.parameters := nil;
  311.         DoParameters := XSErrReported;
  312.         Exit (DoParameters);
  313.     END;
  314.     params^.parameters := Handle(theParams);
  315.     DoParameters := noErr;
  316. END;
  317.  
  318. FUNCTION DoProcessFrame(params: XsitionParamPtr; transitionIntensity,
  319.     maxTransitionIntensity: INTEGER): XsnErr;
  320. {    Perform the effect    }
  321. VAR
  322.     pmStateA,pmStateB,pmStateDest:    GWorldFlags;
  323.     oldGW,destGW:            GWorldPtr;
  324.     oldGD:    GDHandle;
  325.     srcA,srcB,dest:        PixMapHandle;
  326.     stateA,stateB,stateDest:    SignedByte;
  327.     r,bounds:    Rect;
  328.     xSize, ySize, angle:    INTEGER;
  329.     oldFore, oldBack:    RGBColor;
  330.     p:    WipeParamHandle;
  331.     dummy:    BOOLEAN;
  332. BEGIN
  333.     p := WipeParamHandle(params^.parameters);
  334.     
  335.     IF (TestAbort (params)) THEN BEGIN
  336.         DoProcessFrame := XSErrReported;
  337.         Exit (DoProcessFrame);
  338.     END;
  339.     
  340.     srcA := params^.srcA;
  341.     srcB := params^.srcB;
  342.     destGW := params^.destImage;
  343.     
  344. {    Get the image pixmaps, dealing with pre-System 7 GetGWorldPixMap bug    }
  345.     IF (IntegerPtr(SysVersion)^ < $700) THEN
  346.         dest := destGW^.portPixMap
  347.     ELSE
  348.         dest := GetGWorldPixMap (destGW);
  349.     
  350.     r := srcA^^.bounds;
  351.     bounds    := r;
  352.     ySize := r.bottom - r.top;
  353.     xSize := r.right - r.left;
  354.     
  355. {    Spin the beachball    }
  356.     UpdateProgress (params,0,3);
  357.  
  358. {    Calculate the rectangle to copy based on the wipe direction    }
  359.     angle := p^^.angle;
  360.     CASE angle OF
  361.         0:
  362.             BEGIN
  363.                 SetRect (r,0,0,xSize,ySize);
  364.                 r.top := r.bottom - (transitionIntensity * xSize DIV maxTransitionIntensity);
  365.             END;
  366.         90:
  367.             BEGIN
  368.                 SetRect (r,0,0,xSize,ySize);
  369.                 r.right := r.left + (transitionIntensity * xSize DIV maxTransitionIntensity);
  370.             END;
  371.         180:
  372.             BEGIN
  373.                 SetRect (r,0,0,xSize,ySize);
  374.                 r.bottom := r.top + (transitionIntensity * ySize DIV maxTransitionIntensity);
  375.             END;
  376.         270:
  377.             BEGIN
  378.                 SetRect (r,0,0,xSize,ySize);
  379.                 r.left := r.right - (transitionIntensity * xSize DIV maxTransitionIntensity);
  380.             END;
  381.         OTHERWISE
  382.             BEGIN
  383.                 SetRect (r,0,0,xSize,ySize);
  384.                 r.top := r.bottom - (transitionIntensity * xSize DIV maxTransitionIntensity);
  385.             END;
  386.     END;
  387.     
  388. {    spin the beachball    }
  389.     UpdateProgress (params,1,3);
  390.     
  391. { save offscreen pixels state and lock them down for drawing }
  392.     pmStateA := GetPixelsState(srcA);
  393.     dummy := LockPixels (srcA);
  394.     stateA := HGetState (Handle(srcA));
  395.     MoveHHi (Handle(srcA));
  396.     HLock (Handle(srcA));
  397.     
  398.     pmStateB := GetPixelsState(srcB);
  399.     dummy := LockPixels (srcB);
  400.     stateB := HGetState (Handle(srcB));
  401.     MoveHHi (Handle(srcB));
  402.     HLock (Handle(srcB));
  403.     
  404.     pmStateDest := GetPixelsState(dest);
  405.     dummy := LockPixels (dest);
  406.     stateDest := HGetState (Handle(dest));
  407.     MoveHHi (Handle(dest));
  408.     HLock (Handle(dest));
  409.     
  410. {    save drawing state    }
  411.     GetGWorld (oldGW,oldGD);
  412.     SetGWorld (destGW,GetGWorldDevice(destGW));
  413.     GetForeColor (oldFore);
  414.     GetBackColor (oldBack);
  415.     RGBForeColor (RGBColorPtr(RGBBlack)^);
  416.     RGBBackColor (RGBColorPtr(RGBWhite)^);
  417.         
  418. {    copy entire first source image    }
  419.     CopyBits(BitMapHandle(srcA)^^,BitMapHandle(dest)^^,bounds,bounds,srcCopy,nil);
  420.     
  421. {    spin beachball, restoring original graphic state    }
  422.     SetGWorld (oldGW,oldGD);
  423.     UpdateProgress (params,2,3);
  424.     SetGWorld (destGW,GetGWorldDevice(destGW));
  425.     
  426. {    wait for accelerators    }
  427.     WHILE (NOT (QDDone(GrafPtr(destGW)))) DO;
  428.     
  429. {    copy the piece of the second source that we calculated earlier    }
  430.     CopyBits(BitMapHandle(srcB)^^,BitMapHandle(dest)^^,r,r,srcCopy,nil);
  431.     
  432. {    wait for accelerators    }
  433.     WHILE (NOT (QDDone(GrafPtr(destGW)))) DO;
  434.     
  435. {    restore graphic state    }
  436.     RGBForeColor (oldFore);
  437.     RGBBackColor (oldBack);
  438.     
  439.     SetGWorld(oldGW,oldGD);
  440.     UpdateProgress (params,3,3);
  441.     
  442. {    restore offscreen pixmaps' state    }
  443.     HSetState (Handle(srcA),stateA);
  444.     SetPixelsState(srcA,pmStateA);
  445.     HSetState (Handle(srcB),stateB);
  446.     SetPixelsState(srcB,pmStateB);
  447.     HSetState (Handle(dest),stateDest);
  448.     SetPixelsState(dest,pmStateDest);
  449.     
  450.     DoProcessFrame := noErr;
  451. END;
  452.  
  453. END.
  454.